package cn.sanli.manage.service.impl;

import cn.sanli.manage.ex.ServiceException;
import cn.sanli.manage.mapper.data1.*;
import cn.sanli.manage.pojo.dto.User.*;
import cn.sanli.manage.pojo.entity.Organization;
import cn.sanli.manage.pojo.entity.UserInfo;
import cn.sanli.manage.pojo.entity.UserRole;
import cn.sanli.manage.pojo.vo.UserInfoVO;
import cn.sanli.manage.pojo.vo.UserMessage;
import cn.sanli.manage.service.UserInfoService;
import cn.sanli.manage.web.ServiceCode;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import javax.annotation.Resource;
import java.util.*;
import java.util.function.Consumer;

/**
 * 用户信息表(userInfo)表服务实现类
 *
 * @author makejava
 * @since 2023-12-04 15:34:25
 */
@Service("userinfoService")
public class UserInfoServiceImpl implements UserInfoService {
    @Resource
    private UserInfoMapper userInfoMapper;
    @Resource
    private UserRoleMapper userRoleMapper;
    @Resource
    private OrganizationMapper organizationMapper;
    @Resource
    private UserOrganizationMapper userOrganizationMapper;

    /**
     * 通过ID查询单条数据
     *
     * @param id 主键
     * @return 实例对象
     */
    @Override
    public UserInfo queryById(Integer id) {
        return this.userInfoMapper.selectByPrimaryKey(id);
    }

    /**
     * 新增数据
     *
     * @param userInfo 实例对象
     * @return 实例对象
     */
    @Override
    public UserInfo insert(UserInfo userInfo) {
        this.userInfoMapper.insert(userInfo);
        return userInfo;
    }

    /**
     * 修改用户数据
     *
     * @param info 修改信息
     * @return
     */
    @Transactional
    @Override
    public UserInfo update(UpdateUserDTO info) {
        //修改用户信息
        UserInfo userInfo = userInfoMapper.selectByNum(info.getNum());
        //userInfo.setNum(info.getNum());
        userInfo.setUsername(info.getUsername());
        if (info.getCenterName()!=null && info.getCenterName()!=""){
            //获取大口和部门id
            Organization center = organizationMapper.selectCenterByName(info.getCenterName());
            if (center == null) {
                throw new ServiceException(ServiceCode.ERROR_INSERT, "大区名称有误！");
            }
            Organization dept = organizationMapper.selectDeptByName(info.getDeptName(), center.getId());
            if (dept == null) {
                throw new ServiceException(ServiceCode.ERROR_INSERT, "部门名称有误！");
            }
            //修改用户主显组织机构
            List<Integer> organIdList = userOrganizationMapper.selectOrganIdByNum(info.getNum());
            if (!CollectionUtils.isEmpty(organIdList)){
                userOrganizationMapper.deleteByNumAndOrganId(info.getNum(), center.getId());
                userOrganizationMapper.updateOrganId(center.getId(), info.getNum());
            }
            //封装用户数据信息
            userInfo.setCenterId(center.getId());
            userInfo.setDeptId(dept.getId());
        } else if (info.getDeptName()!=null && info.getDeptName()!=""){
            Organization dept = organizationMapper.selectDeptByName(info.getDeptName(), userInfo.getCenterId());
            if (dept == null) {
                throw new ServiceException(ServiceCode.ERROR_INSERT, "部门名称有误！");
            }
            //修改用户主显组织机构
            List<Integer> organIdList = userOrganizationMapper.selectOrganIdByNum(info.getNum());
            if (!CollectionUtils.isEmpty(organIdList)){
                userOrganizationMapper.deleteByNumAndOrganId(info.getNum(), dept.getId());
                userOrganizationMapper.updateOrganId(dept.getId(), info.getNum());
            }
            userInfo.setDeptId(dept.getId());
        }
        userInfo.setCall(info.getCall());
        userInfo.setPhone(info.getPhone());
        userInfo.setWechat(info.getWechat());
        userInfo.setRemark(info.getRemark());
        userInfo.setUpdateTime(new Date());
        if (info.getRoleIdList()!=null && info.getRoleIdList().size()>0) {
            // 删除之前用户所对应的角色数据
            //UserInfo user = userInfoMapper.selectByNum(info.getNum());
            userRoleMapper.deleteByNum(info.getNum());
            // 分配新的角色数据
            List<UserRole> userRoleList = new ArrayList<>();
            List<Integer> roleIdList = info.getRoleIdList();
            //对角色id集合进行排序
            Collections.sort(roleIdList);
            //根据角色分配记分标准
            if (roleIdList.contains(3)) {
                //高层领导
                userInfo.setStandardId(1);
            } else if (roleIdList.contains(5)) {
                //中层领导
                userInfo.setStandardId(2);
            } else if (roleIdList.contains(8)) {
                //普通员工
                userInfo.setStandardId(3);
            }
            this.userInfoMapper.update(userInfo);
            //指定第一个角色id为主权限
            Integer master = roleIdList.get(0);
            UserRole masterRole = new UserRole();
            masterRole.setNum(info.getNum());
            masterRole.setRoleId(master);
            masterRole.setLv(1);
            masterRole.setCreatTime(new Date());
            masterRole.setUpdateTime(new Date());
            //遍历角色id集合
            for (int i = 1; i < roleIdList.size(); i++) {
                UserRole userRole = new UserRole();
                userRole.setNum(info.getNum());
                userRole.setRoleId(roleIdList.get(i));
                userRole.setLv(0);
                userRole.setCreatTime(new Date());
                userRole.setUpdateTime(new Date());
                userRoleList.add(userRole);
            }
            if (roleIdList.size() == 1) {
                // 分配新的角色数据
                userRoleMapper.insertUserRole(masterRole);
            } else if (roleIdList.size() > 1) {
                // 分配新的角色数据
                userRoleMapper.insertUserRole(masterRole);
                userRoleMapper.insertUserRoleList(userRoleList);
            }
        }
        this.userInfoMapper.update(userInfo);
        return this.queryById(userInfo.getId());
    }

    /**
     * 通过主键删除数据
     *
     * @param id 主键
     * @return 是否成功
     */
    @Override
    public boolean deleteById(Integer id) {
        return this.userInfoMapper.deleteByPrimaryKey(id) > 0;
    }

    /**
     * 用户分页列表
     *
     * @param userInfoDto 查询对象
     * @return
     */
    @Override
    public PageInfo<UserInfoVO> findByPage(UserInfoDTO userInfoDto, UserMessage message) {
        PageHelper.startPage(userInfoDto.getPageNum(), userInfoDto.getPageSize());
        int roleId = message.getRoleId();
        // 根据角色获取用户列表
        // 查看全部
        if (roleId == 1 || roleId == 2 || roleId == 7) {
            List<UserInfoVO> userInfoList = userInfoMapper.findByPage(userInfoDto);
            PageInfo pageInfo = new PageInfo(userInfoList);
            return pageInfo;
            //查看大口
        } else if (roleId == 3 || roleId == 4) {
            List<UserInfoVO> userInfoList = userInfoMapper.findByCenter(userInfoDto, message.getCenter_id());
            List<Integer> organIdList = userOrganizationMapper.selectOrganIdByNum(message.getNum());
            //查询代管大区
            if(roleId == 3 && !CollectionUtils.isEmpty(organIdList)){
                organIdList.forEach(organId -> {
                    List<UserInfoVO> otherCenter = userInfoMapper.findByCenter(userInfoDto, organId);
                    userInfoList.addAll(otherCenter);
                });
            }
            PageInfo pageInfo = new PageInfo(userInfoList);
            return pageInfo;
            //查看部门
        } else if (roleId == 5 || roleId == 6) {
            List<UserInfoVO> userInfoList = userInfoMapper.findByDept(userInfoDto, message.getDept_id());
            List<Integer> organIdList = userOrganizationMapper.selectOrganIdByNum(message.getNum());
            //查询代管部门
            if (roleId == 5 && !CollectionUtils.isEmpty(organIdList)){
                organIdList.forEach(organId -> {
                    List<UserInfoVO> otherDept = userInfoMapper.findByDept(userInfoDto, organId);
                    userInfoList.addAll(otherDept);
                });
            }
            PageInfo pageInfo = new PageInfo(userInfoList);
            return pageInfo;
        }
        return null;
    }

    /**
     * 添加用户
     *
     * @param info 用户信息
     */
    @Transactional
    @Override
    public void saveUser(UserDTO info, UserMessage message) {
        int roleId = message.getRoleId();
        // 根据输入的工号查询用户
        UserInfo user = userInfoMapper.selectByNum(info.getNum());
        if (user != null) {
            throw new ServiceException(ServiceCode.ERROR_INSERT, "工号已存在！");
        }
        // 对密码进行加密
        String password = "123456";
        BCryptPasswordEncoder bcryptPasswordEncoder = new BCryptPasswordEncoder();
        String hashPassword = bcryptPasswordEncoder.encode(password);
        //封装用户信息
        UserInfo userInfo = new UserInfo();
        userInfo.setUsername(info.getUsername());
        userInfo.setPassword(hashPassword);
        //获取大口和部门id
        Organization center = organizationMapper.selectCenterByName(info.getCenterName());
        Organization dept = organizationMapper.selectDeptByName(info.getDeptName(), center.getId());
        if (center == null || dept == null) {
            throw new ServiceException(ServiceCode.ERROR_INSERT, "大口或部门名称有误！");
        }
        //封装用户数据信息
        userInfo.setCenterId(center.getId());
        userInfo.setDeptId(dept.getId());
        userInfo.setCall(info.getCall());
        userInfo.setPhone(info.getPhone());
        userInfo.setWechat(info.getWechat());
        userInfo.setNum(info.getNum());
        userInfo.setRemark(info.getRemark());
        userInfo.setCreatTime(new Date());
        userInfo.setUpdateTime(new Date());
        userInfo.setStandardId(3);
        userInfo.setIsDelete(1);
        userInfo.setIsLock(1);
        List<UserRole> userRoleList = new ArrayList<>();
        //获取角色数据
        List<Integer> roleIdList = info.getRoleIdList();
        if (CollectionUtils.isEmpty(roleIdList) || roleIdList.size() == 0) {
            throw new ServiceException(ServiceCode.ERROR_INSERT, "请选择用户角色");
        }
        //对角色id集合进行排序
        Collections.sort(roleIdList);
        //根据角色分配记分标准
        if (roleIdList.contains(3)) {
            //高层领导
            userInfo.setStandardId(1);
        } else if (roleIdList.contains(5)) {
            //中层领导
            userInfo.setStandardId(2);
        } else if (roleIdList.contains(8)) {
            //普通员工
            userInfo.setStandardId(3);
        }
        //指定第一个角色id为主权限
        Integer master = roleIdList.get(0);
        UserRole masterRole = new UserRole();
        masterRole.setNum(info.getNum());
        masterRole.setRoleId(master);
        masterRole.setLv(1);
        masterRole.setCreatTime(new Date());
        masterRole.setUpdateTime(new Date());
        //遍历角色id集合
        for (int i = 1; i < roleIdList.size(); i++) {
            UserRole userRole = new UserRole();
            userRole.setNum(info.getNum());
            userRole.setRoleId(roleIdList.get(i));
            userRole.setLv(0);
            userRole.setCreatTime(new Date());
            userRole.setUpdateTime(new Date());
            userRoleList.add(userRole);
        }

        //添加全部用户
        if (roleId == 1 || roleId == 3) {
            common(userInfo, userRoleList, roleIdList, masterRole);
            //添加大口用户
        } else if (roleId == 4) {
            if (center.getId() != message.getCenter_id()) {
                throw new ServiceException(ServiceCode.ERROR_INSERT, "只能添加相同大口用户！");
            }
            common(userInfo, userRoleList, roleIdList, masterRole);
            //添加部门用户
        } else if (roleId == 5 || roleId == 6) {
            if (center.getId() != message.getCenter_id() || dept.getId() != message.getDept_id()) {
                throw new ServiceException(ServiceCode.ERROR_INSERT, "只能添加相同部门用户！");
            }
            common(userInfo, userRoleList, roleIdList, masterRole);
        } else {
            throw new ServiceException(ServiceCode.ERROR_INSERT, "没有添加用户权限！");
        }
    }

    /**
     * 添加用户的通用方法
     * @param userInfo 用户信息
     * @param userRoleList 用户角色集合
     * @param roleIdList 角色id集合
     * @param masterRole 主权限
     */
    private void common(UserInfo userInfo, List<UserRole> userRoleList, List<Integer> roleIdList, UserRole masterRole) {
        if (roleIdList.size() == 1) {   //添加主权限
            //添加用户
            userInfoMapper.insertSelective(userInfo);
            //添加用户角色
            userRoleMapper.insertUserRole(masterRole);
        } else if (roleIdList.size() > 1) { //添加主权限和其它权限
            //添加用户
            userInfoMapper.insertSelective(userInfo);
            //添加用户角色
            userRoleMapper.insertUserRole(masterRole);
            userRoleMapper.insertUserRoleList(userRoleList);
        }
    }

    /**
     * 账号锁定
     *
     * @param userIsLockDto 用户账号有无被锁定
     */
    @Override
    public void updateIsLock(UserIsLockDTO userIsLockDto) {
        userInfoMapper.updateIsLockById(userIsLockDto.getIsLock(), userIsLockDto.getId());
    }

    /**
     * 删除用户
     *
     * @param id 用户id
     */
    @Override
    public void updateIsDelete(Integer id, UserMessage message) {
        int roleId = message.getRoleId();
        //获取用户信息
        UserInfo userInfo = userInfoMapper.selectByPrimaryKey(id);
        //获取用户角色
        UserRole userRole = userRoleMapper.selectByNum(userInfo.getNum());
        if (message.getNum().equals(userInfo.getNum()) || ((userRole.getRoleId() <= roleId && roleId != 1))) {
            throw new ServiceException(ServiceCode.ERROR_DELETE, "不能删除自己或更高权限用户");
        }else if ((userRole.getRoleId()==2 || userRole.getRoleId()==7) && roleId != 1){
            throw new ServiceException(ServiceCode.ERROR_DELETE, "不能删除更高权限用户");
        }
        //删除用户
        userInfoMapper.updateIsDeleteById(id);
    }

    /**
     * 批量删除
     *
     * @param info 用户id集合
     */
    @Override
    public void batchDelete(BatchDeleteUserDTO info, UserMessage message) {
        int roleId = message.getRoleId();
        List<Integer> idList = info.getIdList();
        idList.forEach(id -> {
            //获取用户信息
            UserInfo userInfo = userInfoMapper.selectByPrimaryKey(id);
            //获取用户角色
            UserRole userRole = userRoleMapper.selectByNum(userInfo.getNum());
            if (message.getNum().equals(userInfo.getNum()) || ((userRole.getRoleId() <= roleId && roleId != 1))) {
                throw new ServiceException(ServiceCode.ERROR_DELETE, "不能删除自己或更高权限用户");
            }else if ((userRole.getRoleId()==2 || userRole.getRoleId()==7) && roleId != 1){
                throw new ServiceException(ServiceCode.ERROR_DELETE, "不能删除更高权限用户");
            }
        });
        //批量删除
        userInfoMapper.batchDelete(idList);
    }

    /**
     * 重置密码
     *
     * @param id 用户id
     */
    @Override
    public void resetPassWord(Integer id) {
        //重置初始密码123456
        String password = "123456";
        BCryptPasswordEncoder bcryptPasswordEncoder = new BCryptPasswordEncoder();
        String hashPassword = bcryptPasswordEncoder.encode(password);
        userInfoMapper.resetPassWord(hashPassword, id);
    }

    /**
     * 修改当前登录用户
     *
     * @param info    修改信息
     * @param message 登录用户信息
     * @return
     */
    @Override
    public UserInfo updateLoginUser(UpdateLoginUserDTO info, UserMessage message) {
        // 获取当前登录用户信息
        UserInfo userInfo = userInfoMapper.selectByNum(message.getNum());
        userInfo.setNum(message.getNum());
        userInfo.setUsername(info.getUsername());
        // 对密码进行加密
        String password = info.getPassword();
        BCryptPasswordEncoder bcryptPasswordEncoder = new BCryptPasswordEncoder();
        String hashPassword = bcryptPasswordEncoder.encode(password);
        userInfo.setPassword(hashPassword);
        //获取大口和部门id
        /*Organization center = organizationMapper.selectCenterByName(info.getCenterName());
        Organization dept = organizationMapper.selectDeptByName(info.getDeptName(), center.getId());
        if (center == null || dept == null) {
            throw new ServiceException(ServiceCode.ERROR_INSERT, "大口或部门名称有误！");
        }
        userInfo.setCenterId(center.getId());
        userInfo.setDeptId(dept.getId());*/
        //封装数据信息
        userInfo.setCall(info.getCall());
        userInfo.setPhone(info.getPhone());
        userInfo.setWechat(info.getWechat());
        userInfo.setRemark(info.getRemark());
        userInfo.setUpdateTime(new Date());
        this.userInfoMapper.update(userInfo);
        return this.queryById(userInfo.getId());
    }

    /**
     * 查询工号是否存在
     *
     * @param num 工号
     */
    @Override
    public void findByNum(String num) {
        // 根据输入的工号查询用户
        UserInfo user = userInfoMapper.selectByNum(num);
        if (user != null) {
            throw new ServiceException(ServiceCode.ERROR_INSERT, "工号已存在！");
        }
    }

    /**
     * 查询用户信息
     *
     * @param num 工号
     * @return
     */
    @Override
    public UserInfoVO findUserInfo(String num) {
        return userInfoMapper.selectAllByNum(num);
    }

    /*@Override
    public void updateUserStandard(UserStandardDTO info) {
        userInfoMapper.updateStandardIdByNum(info.getStandardId(), info.getNum());
    }*/
}

